🔍 Step-by-Step Branch and Bound Demo
Click "Start Demo" to begin step-by-step visualization
Algorithm Progress:
1. Display input items
2. Sort by value/weight ratio
3. Explore decision tree
4. Display result
Current Items (Sorted):
Algorithm State:
| Node ID |
Level |
Profit |
Weight |
Bound |
Action |
Decision Tree:
🎮 Practice Knapsack with Branch and Bound
Test Cases
Example 1: N=4, W=10, weights=[2,3,5,4], values=[40,50,100,60] → 190.00
Example 2: N=4, W=10, weights=[2,3,4,1], values=[10,15,20,5] → 50.00
📊 Algorithm Analysis
Branch and Bound Process
- Sort Items: By value-to-weight ratio in descending order
- Initialize: Start with root node (level=-1, profit=0, weight=0)
- Explore Nodes: For each node, create branches for including/excluding the next item, compute bound, and prune if bound ≤ maxProfit
- Output: Maximum profit, rounded to two decimal places
struct Item {
int weight, value;
double ratio;
};
struct Node {
int level, profit, weight;
double bound;
};
double bound(Node u, int n, int W, vector- & items) {
if (u.weight >= W) return 0;
double profit_bound = u.profit;
int j = u.level + 1;
int totweight = u.weight;
while (j < n && totweight + items[j].weight <= W) {
totweight += items[j].weight;
profit_bound += items[j].value;
j++;
}
if (j < n) {
profit_bound += (W - totweight) * items[j].ratio;
}
return profit_bound;
}
int main() {
int N, W;
cin >> N >> W;
vector<int> weights(N), values(N);
for (int i = 0; i < N; i++) cin >> weights[i];
for (int i = 0; i < N; i++) cin >> values[i];
vector
- items(N);
for (int i = 0; i < N; i++) {
items[i].weight = weights[i];
items[i].value = values[i];
items[i].ratio = (double)values[i] / weights[i];
}
sort(items.begin(), items.end(), [](Item a, Item b) {
return a.ratio > b.ratio;
});
queue Q;
Node u, v;
u.level = -1; u.profit = 0; u.weight = 0;
u.bound = bound(u, N, W, items);
double maxProfit = 0.0;
Q.push(u);
while (!Q.empty()) {
u = Q.front(); Q.pop();
if (u.level == N - 1) continue;
v.level = u.level + 1;
v.weight = u.weight + items[v.level].weight;
v.profit = u.profit + items[v.level].value;
if (v.weight <= W && v.profit > maxProfit) maxProfit = v.profit;
v.bound = bound(v, N, W, items);
if (v.bound > maxProfit) Q.push(v);
v.weight = u.weight;
v.profit = u.profit;
v.bound = bound(v, N, W, items);
if (v.bound > maxProfit) Q.push(v);
}
cout << fixed << setprecision(2) << maxProfit;
return 0;
}
Time Complexity
O(2^N)
Worst case, reduced by pruning
Space Complexity
O(N)
For queue and recursion stack
Key Points
- Branch and Bound: Optimizes by pruning suboptimal branches
- Bound Function: Estimates maximum possible profit
- Applications: Resource allocation, scheduling
- Limitation: Exponential time in worst case